package ysgrpc

import (
	"context"
	"gitee.com/kmyss/gf-ex/yslog"
	"github.com/gogf/gf/v2/errors/gcode"
	"github.com/gogf/gf/v2/errors/gerror"
	"github.com/gogf/gf/v2/os/glog"
	"google.golang.org/grpc"
	"net"
)

type ServerCfg struct {
	Host string
}

func getServerConnCfg(ctx context.Context) *ServerCfg {
	host := FlagHost(ctx).GetVar()

	return &ServerCfg{
		Host: host.String(),
	}
}

func NewServerWithCustom(ctx context.Context, server *grpc.Server) *Server {
	s := &Server{
		cfg: getServerConnCfg(ctx),
		ctx: ctx,
		s:   server,
	}
	return s
}
func NewServer(ctx context.Context) *Server {
	s := NewServerWithCustom(ctx, grpc.NewServer())
	return s
}

type RegistrarHandler func(registrar grpc.ServiceRegistrar)

type Server struct {
	rs  []RegistrarHandler
	s   *grpc.Server
	cfg *ServerCfg
	ctx context.Context
	l   *glog.Logger // 内部日志，使用 log 函数调用
}

func (s *Server) log() *glog.Logger {
	if s.l == nil {
		s.l = yslog.Log(CONFIG_NODE_NAME)
	}
	return s.l
}

func (s *Server) Server() *grpc.Server {
	return s.s
}

func (s *Server) AddRegistrarHandler(handler RegistrarHandler) {
	s.rs = append(s.rs, handler)
}

// Run 启动 grpc 服务，阻塞
func (s *Server) Run(force ...bool) error {
	lis, err := net.Listen("tcp", s.cfg.Host)
	if err != nil {
		s.log().Fatalf(s.ctx, "启动 TCP 监听失败: %v", err)
	}
	defer lis.Close()

	for _, r := range s.rs {
		r(s.s)
	}

	if len(force) == 0 || !force[0] {
		if len(s.s.GetServiceInfo()) == 0 {
			return gerror.NewCode(gcode.CodeInternalError, "没有任何 GRPC Server 注册！")
		}
	}

	s.log().Infof(s.ctx, "GRPC 服务启动在: %v", lis.Addr())
	return s.s.Serve(lis)
}

// Stop 关闭 grpc 服务
func (s *Server) Stop() {
	s.s.Stop()
}
